package com.project.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.project.dto.MaterialRequestDTO;
import com.project.dto.MaterialRequestPageDTO;
import com.project.entity.*;
import com.project.enums.ApprovalsFinalStatusEnum;
import com.project.enums.DecisionEnum;
import com.project.enums.RequestStatusEnum;
import com.project.mapper.*;
import com.project.entity.MaterialRequests;
import com.project.entity.Materials;

import com.project.mapper.MeterialRequestsMapper;
import com.project.service.MeterialRequestsService;
import com.project.vo.*;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.function.Consumer;

@Service
public class MeterialRequestsServiceImpl extends ServiceImpl<MeterialRequestsMapper, MaterialRequests> implements MeterialRequestsService {
    @Autowired
    private MeterialRequestsMapper meterialRequestsMapper;
    @Autowired
    private MaterialsMapper materialsMapper;

    @Autowired
    private UserMapper userMapper;
    @Autowired
    private ApprovalsMapper approvalsMapper;
    @Autowired
    private ApprovalStepsMapper     approvalStepsMapper;


    /**
     *根据申请ID查询详细信息（待完善x4）
     * @param id 申请id
     * @return 申请详细信息vo
     */
    @Override
    public MaterialRequestVO getByRequestId(Integer id) {
        //判断用户权限

        //构建返回类型
        MaterialRequestVO materialRequestVO=new MaterialRequestVO();
        //查询材料申请表
        MaterialRequests materialRequests = getById(id);

        BeanUtils.copyProperties(materialRequests,materialRequestVO);

        //根据材料id查询材料具体信息(待完善)
        Materials materials=materialsMapper.selectById(materialRequests.getMaterialId());
        materialRequestVO.setMaterialName(materials.getName());
        materialRequestVO.setMaterialCode(materials.getMaterialCode());
        materialRequestVO.setSpecification(materials.getSpecification());
        materialRequestVO.setUnit(materials.getUnit());
        //查询applicant_name
        materialRequestVO.setApplicantName(userMapper.selectById(materialRequests.getApplicantId()).getRealName());
        //封装数据
        materialRequestVO.setMaterialId(materials.getMaterialId());
        materialRequestVO.setMaterialName(materials.getName());
        materialRequestVO.setMaterialCode(materials.getMaterialCode());
        materialRequestVO.setSpecification(materials.getSpecification());
        materialRequestVO.setUnit(materials.getUnit());
        //查询最终请求是否通过
        Integer status=approvalsMapper.selectByRequestId(id);
        //通过枚举获取状态名称
        materialRequestVO.setFinalStatusName(ApprovalsFinalStatusEnum.getStatusName(status));

        return materialRequestVO;
    }

    @Override
    public Long getPendingCount() {
        LambdaQueryWrapper<MaterialRequests> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(MaterialRequests::getStatus,RequestStatusEnum.PENDING.getCode());
        return count(wrapper);
    }

    /**
     * 申请列表分页查询
     *
     * @param materialRequestPageDTO
     * @return
     */
    @Override
    public MaterialRequestPageVO listPage(MaterialRequestPageDTO materialRequestPageDTO) {
        //权限判断，申请人只能看到自己的，材料员，项目经理能看到所有

        LambdaQueryWrapper<MaterialRequests> wrapper = new LambdaQueryWrapper<>();
        LambdaQueryWrapper<Users> userWrapper = new LambdaQueryWrapper<>();
        userWrapper.eq(Users::getRealName,materialRequestPageDTO.getApplicantName());

        List<Users> users = userMapper.selectList(userWrapper);
        List<Integer> ids=new ArrayList<>();
        users.forEach(user -> ids.add(user.getUserId()));
        wrapper.in(ids!= null&&ids.size()>0, MaterialRequests::getApplicantId, ids)
               .eq(materialRequestPageDTO.getMaterialId() != null, MaterialRequests::getMaterialId, materialRequestPageDTO.getMaterialId())
               .eq(materialRequestPageDTO.getTeamId()!=null,MaterialRequests::getMaterialId, materialRequestPageDTO.getMaterialId())
               .le(materialRequestPageDTO.getEndDate()!=null,MaterialRequests::getCreateTime, materialRequestPageDTO.getEndDate())
               .ge(materialRequestPageDTO.getStartDate()!=null,MaterialRequests::getCreateTime, materialRequestPageDTO.getStartDate());
        Page<MaterialRequests> page=new Page<>(materialRequestPageDTO.getPage(), materialRequestPageDTO.getSize());
        List<MaterialRequests> list = meterialRequestsMapper.selectPage(page, wrapper).getRecords();

        MaterialRequestPageVO materialRequestPageVO =new MaterialRequestPageVO();
        BeanUtils.copyProperties(page, materialRequestPageVO);

        List<MaterialRequestVO> voList=new ArrayList<>();
        //根据材料请求id获取材料请求
        list.forEach(mrv -> voList.add(getByRequestId(mrv.getRequestId())));

        //总封装
        materialRequestPageVO.setMaterialRequestVOList(voList);
        return materialRequestPageVO;
    }

    /**
     * 根据审批实例查询Id查询申请表
     * @param approvalId
     * @return
     */
    @Override
    public Approvals_DetailVO getByApprovalsId(Integer approvalId) {
        Approvals_DetailVO adv=new Approvals_DetailVO();
        //获取审批实例
        //Approvals approvals = approvalsMapper.selectById(approvalId);
        Approvals approvals = approvalsMapper.selectByApprovalId(approvalId);
        //获取申请表vo
        MaterialRequestVO request = getByRequestId(approvals.getRequestId());

        BeanUtils.copyProperties(request,adv);

        LambdaQueryWrapper<ApprovalSteps> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(ApprovalSteps::getApprovalId,approvalId);
        List<ApprovalSteps> steps=approvalStepsMapper.selectApproovalStepsByApprovalId(approvalId);
        List<Approval_stepsVO> stepsVOS=new ArrayList<>();
        steps.forEach(new Consumer<ApprovalSteps>() {
            @Override
            public void accept(ApprovalSteps step) {
                Approval_stepsVO stepsVO=new Approval_stepsVO();
                //BeanUtils.copyProperties(step,stepsVO);
                stepsVO.setApprovalId(step.getApprovalId());
                stepsVO.setApproverName(userMapper.selectById(step.getApproverId()).getRealName());
                stepsVO.setDecisionName(DecisionEnum.getStatusName(step.getDecision()));
                stepsVO.setComment(step.getComment());
                stepsVO.setApprovedAt(step.getApprovedAt());
                stepsVOS.add(stepsVO);
            }
        });
        adv.setApprovals(stepsVOS);
        adv.setFinalStatusName(ApprovalsFinalStatusEnum.getStatusName(approvals.getFinalStatus()));
        adv.setFinishTime(approvals.getFinishTime());
        return adv;
    }

    /**
     * 创建申请表
     * @param materialRequestDTO
     */
    @Transactional
    @Override
    public void createRequest(MaterialRequestDTO materialRequestDTO) {
        /**
         * 业务规则
         *
         */
        //插入材料申请表
        MaterialRequests materialRequests=new MaterialRequests();
        BeanUtils.copyProperties(materialRequestDTO,materialRequests);
        materialRequests.setCreateTime(LocalDateTime.now());
        materialRequests.setUpdateTime(LocalDateTime.now());
        materialRequests.setStatus(0);
        materialRequests.setApplicantId(materialRequestDTO.getUserId());
        materialRequests.setTeamId(materialRequestDTO.getUserId());
        //插入获取申请id
        meterialRequestsMapper.insert(materialRequests);
        Integer request_id=materialRequests.getRequestId();

        //插入申请实例表
        Approvals approvals=new Approvals();
        approvals.setRequestId(request_id);
        approvals.setApprovalType(2);
        Integer userType = userMapper.selectById(materialRequestDTO.getUserId())
                                     .getUserType();
        //判断用户类型，如果是班主，步骤为1，如果是材料员，步骤为2
        if(userType==1){
            approvals.setCurrentStep(2);
        }else if(userType==2){
            approvals.setCurrentStep(3);
        }else{
            throw new RuntimeException("当前用户不能操作");
        }
        //进行中
        approvals.setFinalStatus(0);
        approvals.setUpdateTime(LocalDateTime.now());
        approvals.setCreateTime(LocalDateTime.now());
        approvalsMapper.insert(approvals);
        Integer approval_id=approvals.getApprovalId();
        //插入材料申请步骤
        ApprovalSteps approvalSteps=new ApprovalSteps();
        approvalSteps.setDecision(0);//未审批
        approvalSteps.setApprovalId(approval_id);
        approvalSteps.setStepOrder(1);
        //判断申请用户，如果是班主，材料员审批，如果是材料员，项目经理审批
        if(userType==1){
            approvalSteps.setApproverId(2);
        }else if(userType==2){
            approvalSteps.setApproverId(1);
        }
        approvalSteps.setDecision(null);
        approvalSteps.setComment(null);
        approvalSteps.setApprovedAt(null);
        approvalStepsMapper.insert(approvalSteps);

    }
}
